<template>
    <el-card :body-style="{ padding: 0 }">
        <div class="conation">
            <div class="loading-conation" ref="imgConationRef" v-show="loading">
                <div class="loader"></div>
            </div>

            <div class="img-conation" v-show="!loading">
                <img ref="imgRef" :src="props.url" />
            </div>
            <div class="num" v-if="props.num && props.num > 1">
                <div class="num-bg"></div>
                <el-icon size="20"><CopyDocument /></el-icon>{{ props.num }}
            </div>
            <div class="download" v-if="props.progress">
                <el-icon size="20"><Download /></el-icon>
                <span v-if="props.progress.value.state === 'start'">准备</span>
                <span v-if="props.progress.value.state === 'loading'">{{
                    props.progress.value.progress
                }}</span>
                <span v-if="props.progress.value.state === 'end'">完成</span>
            </div>
        </div>
        <div class="img-body">
            <div class="sheet-author">
                <div class="sheet-author-avatar">
                    <v-img
                        class="img-item"
                        width="50"
                        cover
                        height="50"
                        :src="props.avatar"
                        :lazy-src="props.avatar"
                    />
                </div>
                <div class="sheet-author-right">
                    <el-text truncated style="width: 100%">
                        {{ props.title }}
                    </el-text>
                    <el-text truncated style="width: 100%">
                        {{ props.name }}
                    </el-text>
                </div>
            </div>
            <el-divider style="margin: 5px 0" />
            <div>
                <el-button @click="emits('click')">下载</el-button>
            </div>
        </div>
    </el-card>
</template>

<script setup lang="ts">
import { watch } from "vue"
import { defineProps, type Ref, defineEmits, ref, onMounted } from "vue"

const loading = ref<boolean>(true)
const imgConationRef = ref<HTMLImageElement>()
const imgRef = ref<HTMLImageElement>()
const props = defineProps<{
    url: string
    lazy?: boolean
    num?: number
    title?: string
    name?: string
    avatar?: string
    progress?: Ref<{
        state: string
        progress: number
    }>
}>()

watch(
    () => props.url,
    (state) => {
        loading.value = true
        imageLoad(state)
    },
)
const emits = defineEmits<(event: "click") => void>()

const imageLoad = (url: string): void => {
    const img = imgRef.value as HTMLImageElement

    img.src = url
    img.onload = () => {
        loading.value = false
    }

    img.style.width = "100%"
    img.style.height = "350px"
    img.style.objectFit = "cover"
}

onMounted(() => {
    const observe = new IntersectionObserver((entries, ob) => {
        const entre = entries[0]
        if (entre.isIntersecting) {
            imageLoad(props.url)
            ob.unobserve(imgConationRef.value as Element)
        }
    })

    observe.observe(imgConationRef.value as Element)
})
</script>
<style lang="scss">
.sheet-author {
    img {
        width: 50px;
        height: 50px;
    }
}
</style>

<style lang="scss" scoped>
.img-body {
    padding: 10px;
}

.sheet-author {
    display: flex;

    gap: 10px;
    img {
        width: 50px;
        height: 50px;
    }

    .sheet-author-right {
        flex: 1;
    }
}

.conation {
    position: relative;
    --conation-height: 350px;
    width: inherit;

    .img-conation {
        overflow: hidden;
        height: var(--conation-height);
        img {
            height: var(--conation-height);
            transition: transform 0.4s ease-in-out;
            &:hover {
                transform: scale(1.2);
                transition: transform 0.4s ease-in-out;
            }
        }
    }

    .download,
    .num {
        position: absolute;
        z-index: 1;

        height: 30px;
        display: flex;
        justify-content: center;
        align-items: center;
        gap: 5px;
        color: #fff;
        opacity: 0.7;
        border-radius: 5px;
    }
    .download {
        background-color: #13d14c;
        top: 10px;
        left: 10px;
        width: 80px;
    }
    .num {
        background-color: #6d90d6;
        top: 10px;
        right: 10px;
        width: 60px;
    }
    /* height: var(--conation-height); */
    .loading-conation {
        display: flex;

        width: inherit;
        height: var(--conation-height);
        .loader {
            margin: auto;
            width: fit-content;
            font-weight: bold;
            font-family: sans-serif;
            font-size: 30px;
            padding-bottom: 8px;
            background: linear-gradient(currentColor 0 0) 0 100%/0% 3px
                no-repeat;
            animation: l2 2s linear infinite;
        }
        .loader:before {
            content: "Loading...";
        }
        @keyframes l2 {
            to {
                background-size: 100% 3px;
            }
        }
    }
}

/* HTML: <div class="loader"></div> */
/* HTML: <div class="loader"></div> */
</style>
